import "@pnp/common";
import "@pnp/odata";
import "@pnp/logging";
import { sp } from "@pnp/sp/presets/all";
import { ISearchResult as SPISearchResult } from "@pnp/sp/search/types";

import "@pnp/sp/webs";
import "@pnp/sp/lists";
import "@pnp/sp/items";
import "@pnp/sp/search";
import "@pnp/sp/attachments";
import "@pnp/sp/files";
import "@pnp/sp/folders";
import "@pnp/sp/site-users/web";

// 定义接口
interface ICurrentUser {
  Id: number;
  Title: string;
  Email: string;
  LoginName: string;
}

interface ISearchResponse {
  results: SPISearchResult[];
  totalCount: number;
  currentPage: number;
  pageSize: number;
}

interface ISearchParams {
  Querytext: string;
  SelectProperties: string[];
  RowLimit: number;
  StartRow: number;
  TrimDuplicates: boolean;
  EnableInterleaving: boolean;
  EnableNicknames: boolean;
  EnablePhonetic: boolean;
  HitHighlightedMultivaluePropertyLimit: number;
  HitHighlightedProperties: string[];
  SortList?: Array<{
    Property: string;
    Direction: 0 | 1;  // 0 for ascending, 1 for descending
  }>;
  SourceId?: string;
  ClientType?: string;
  EnableQueryRules?: boolean;
}

interface IPersonSearchResult {
  accountName: string;
  name: string;
  preferredName: string;
  email: string;
  jobTitle: string;
  department: string;
  pictureUrl: string;
  workPhone: string;
  mobilePhone: string;
  aboutMe: string;
  userName: string;
  lastModified: string;
  rawData: Record<string, unknown>;
}

interface IPersonSearchResponse {
  results: IPersonSearchResult[];
  totalCount: number;
  debugInfo?: Record<string, unknown>;
}

interface ISiteSearchResult {
  SiteId?: string;
  SiteName?: string;
  SiteUrl?: string;
  Title?: string;
  Description?: string;
  WebTemplate?: string;
  LastModifiedTime?: string | Date;
  Created?: string | Date;
  Author?: string;
  SiteLogo?: string;
  IsHubSite?: boolean;
  HubSiteId?: string;
  ParentSiteUrl?: string;
  LikesCount?: number;
  ViewsRecent?: number;
  CompatibilityLevel?: number;
  Rank?: number;
  DocId?: number;
  WorkId?: number;
  Path?: string;
  Size?: number;
  Culture?: string;
  Write?: Date;
  CollapsingStatus?: number;
  [key: string]: unknown;
}

interface ISiteSearchResponse {
  results: ISiteSearchResult[];
  totalCount: number;
}

sp.setup({
  sp: {
    baseUrl: "https://zhi1soft.sharepoint.cn",
    headers: {
      Accept: "application/json",
    },
  },
});

export default class Api {
  //获取用户详情
  public static async _getcurrentUser(): Promise<ICurrentUser | undefined> {
    try {
      return await sp.web.currentUser();
    } catch (e) {
      console.log(e);
      return undefined;
    }
  }

  public static async _getSearchData(
    queryText: string = "",
    rowLimit: number = 50,
    sortBy: "recent" | "created" | true | false | "none" = "none",
    fileType?: "word" | "excel" | "powerpoint" | "all" | "site" | "file",
    currentPage: number = 1,
    timeRange?: "24hours" | "lastWeek" | "lastMonth" | "3months" | "1year" | "over1year"| undefined
  ): Promise<ISearchResponse> {
    try {
      console.log(
        `Search parameters - queryText: ${queryText}, rowLimit: ${rowLimit}, sortBy: ${sortBy}, fileType: ${fileType}, page: ${currentPage}, timeRange: ${timeRange}`
      );
  
      // 根据 fileType 构建搜索条件
      let searchConditions: string;
  
      switch (fileType) {
        case "word":
          searchConditions = "(IsDocument=1) AND (FileExtension:docx OR FileExtension:doc)";
          break;
        case "excel":
          searchConditions = "(IsDocument=1) AND (FileExtension:xlsx OR FileExtension:xls)";
          break;
        case "powerpoint":
          searchConditions = "(IsDocument=1) AND (FileExtension:pptx OR FileExtension:ppt)";
          break;
        case "site":
          searchConditions = "(contentclass:STS_Web OR contentclass:STS_Site)";
          break;
        case "file":
          searchConditions = "(IsDocument=1)";
          break;
        case "all":
          searchConditions = "(IsDocument=1 OR contentclass:STS_Web OR contentclass:STS_Site)";
          break;
        default:
          searchConditions = "(IsDocument=1 OR contentclass:STS_Web OR contentclass:STS_Site)";
          break;
      }
  
       // 2. 安全的时间范围条件生成
    let timeRangeCondition = "";
    if (timeRange) { // 仅当timeRange有值时才处理
      const now = new Date();
      let startDate: Date = new Date();
      let endDate: Date | null = null;

      switch (timeRange) {
        case "24hours":
          startDate = new Date(now.getTime() - 24 * 60 * 60 * 1000);
          break;
        case "lastWeek":
          startDate = new Date(now.getTime() - 7 * 24 * 60 * 60 * 1000);
          break;
        case "lastMonth":
          startDate = new Date(now.getFullYear(), now.getMonth() - 1, now.getDate());
          break;
        case "3months":
          startDate = new Date(now.getFullYear(), now.getMonth() - 3, now.getDate());
          break;
        case "1year":
          startDate = new Date(now.getFullYear() - 1, now.getMonth(), now.getDate());
          break;
        case "over1year":
          endDate = new Date(now.getFullYear() - 1, now.getMonth(), now.getDate());
          startDate = new Date(0);
          break;
        default:
          // 处理未定义的情况
          break;
      }

      const startDateString = startDate.toISOString().split('T')[0];
      timeRangeCondition = `AND LastModifiedTime>="${startDateString}"`;
      
      if (endDate) {
        const endDateString = endDate.toISOString().split('T')[0];
        timeRangeCondition += ` AND LastModifiedTime<="${endDateString}"`;
      }
    }

    // 3. 安全构建查询字符串
    const fullQuery = [
      searchConditions,
      timeRangeCondition,
      queryText ? `AND (Filename:*${queryText}* OR Title:*${queryText}* OR HitHighlightedSummary:*${queryText}* OR SiteName:*${queryText}*)` : ""

    ].filter(Boolean).join(" ").trim();

      console.log("Generated KQL query:", fullQuery);

      const selectProperties = [
        "Title",
        "Path",
        "Filename",
        "FileExtension",
        "FileType",
        "Size",
        "Created",
        "Modified",
        "Author",
        "Editor",
        "SiteName",
        "ContentType",
        "IsDocument",
        "UniqueId",
        "PictureThumbnailURL",
        "LastModifiedTime",
        "FileRef",
        "File_x0020_Size",
        "Content",
        "HitHighlightedSummary",
        "contentclass",
        "WebId",
        "SiteId",
        "SiteLogo",
        "SiteUrl",
        "WebTemplate",
        "Description",
        "ParentLink",
        "Manager",
        "SiteOwner",
        "SiteMembers",
        "SiteAdmins",
        "LikesCount",
        "ViewsLifeTime",
        "ViewsRecent",
        "LastItemModifiedDate",
        "LastItemUserModifiedDate",
      ];

      // 计算起始行（分页核心逻辑）
      const startRow = (currentPage - 1) * rowLimit;

      const searchParams: ISearchParams = {
        Querytext: fullQuery,
        SelectProperties: selectProperties,
        RowLimit: rowLimit,
        StartRow: startRow,
        TrimDuplicates: false,
        EnableInterleaving: true,
        EnableNicknames: true,
        EnablePhonetic: true,
        HitHighlightedMultivaluePropertyLimit: 0,
        HitHighlightedProperties: ["Content", "Title", "Filename", "SiteName"],
      };

      // 根据排序参数设置排序规则
      if (sortBy === "created" || sortBy === "recent") {
        searchParams.SortList = [
          {
            Property: sortBy === "recent" ? "LastModifiedTime" : "Created",
            Direction: sortBy === "recent" ? 1 : 0, // 1表示降序（最新在前），0表示升序
          },
        ];
      }
      if (sortBy === true) {
        searchParams.SortList = [
          {
            Property: "LastModifiedTime",
            Direction: 1,
          },
        ];
      }
      if (sortBy === false) {
        searchParams.SortList = [
          {
            Property: "LastModifiedTime",
            Direction: 0,
          },
        ];
      }

      console.log(
        "Search API parameters:",
        JSON.stringify(searchParams, null, 2)
      );

      const results = await sp.search(searchParams);

      console.log("Raw search results:", results);

      const processedResults =
        results.PrimarySearchResults?.map((item: SPISearchResult) => {
          // 判断是否是站点
          if (
            item.contentclass === "STS_Web" ||
            item.contentclass === "STS_Site"
          ) {
            return {
              ...item,
              FileCategory: "Site",
              IsSite: true,
            };
          }

          // 处理文档类型
          let fileCategory: string;
          const ext = (item.FileExtension || "").toLowerCase();

          if (ext === "docx" || ext === "doc") {
            fileCategory = "Word";
          } else if (ext === "xlsx" || ext === "xls") {
            fileCategory = "Excel";
          } else if (ext === "pptx" || ext === "ppt") {
            fileCategory = "PowerPoint";
          } else if (ext === "pdf") {
            fileCategory = "PDF";
          } else if (ext === "txt") {
            fileCategory = "Text";
          } else {
            fileCategory = "Other";
          }

          return {
            ...item,
            FileCategory: fileCategory,
            IsSite: false,
          };
        }) || [];

      console.log("Processed results count:", processedResults.length);

      return {
        results: processedResults,
        totalCount: results.TotalRows,
        currentPage: currentPage,
        pageSize: rowLimit,
      };
    } catch (error) {
      console.error("搜索API错误:", error);
      throw error;
    }
  }

  /**
   * 搜索SharePoint人员信息
   * @param queryText 搜索文本（可选）
   * @param rowLimit 返回结果数量限制（默认50）
   * @param sortByRecent 是否按最后修改时间排序（默认false）
   * @returns 包含搜索结果和总数的对象
   */
  public static async getPeopleSearchData(
    queryText: string = "",
    rowLimit: number = 50,
    sortByRecent: boolean = false
  ): Promise<IPersonSearchResponse> {
    try {
      // 组合查询条件 - 使用更兼容的语法
      const fullQuery = `(contentclass:Person OR contentclass:STS_User) ${
        queryText
          ? `AND (Name:"${queryText}" OR AccountName:"${queryText}" OR WorkEmail:"${queryText}" OR UserName:"${queryText}")`
          : ""
      }`;

      // 定义要返回的人员属性字段
      const selectProperties = [
        "AccountName",
        "Name",
        "PreferredName",
        "WorkEmail",
        "JobTitle",
        "Department",
        "PictureURL",
        "UserProfile_GUID",
        "SPS-Department",
        "SPS-JobTitle",
        "SPS-Location",
        "WorkPhone",
        "MobilePhone",
        "AboutMe",
        "UserName",
        "LastModifiedTime",
      ];

      // 构建搜索参数 - 移除了无效的ResultSourceId
      const searchParams: any = {
        Querytext: fullQuery,
        SelectProperties: selectProperties,
        RowLimit: rowLimit,
        TrimDuplicates: false,
        SourceId: "b09a7990-05ea-4af9-81ef-edfab16c4e31", // 保留有效的SourceId
        ClientType: "ContentSearchRegular",
        EnableQueryRules: true,
      };

      // 如果需要按最近修改时间排序
      if (sortByRecent) {
        searchParams.SortList = [
          {
            Property: "LastModifiedTime",
            Direction: "0", // 降序（最新的在前）
          },
        ];
      }

      // console.log("执行人员搜索，参数:", JSON.stringify(searchParams, null, 2));

      // 执行搜索查询
      const results = await sp.search(searchParams);

      console.log("收到搜索结果，原始数据:", results);

      // 处理结果
      const processedResults =
        results.PrimarySearchResults?.map((item: Record<string, unknown>) => {
          const result: IPersonSearchResult = {
            accountName: (item.AccountName as string) || "",
            name: (item.Name as string) || "",
            preferredName: (item.PreferredName as string) || "",
            email: (item.WorkEmail as string) || "",
            jobTitle: ((item.JobTitle as string) || (item["SPS-JobTitle"] as string) || ""),
            department: ((item.Department as string) || (item["SPS-Department"] as string) || ""),
            pictureUrl: (item.PictureURL as string) || "",
            workPhone: (item.WorkPhone as string) || "",
            mobilePhone: (item.MobilePhone as string) || "",
            aboutMe: (item.AboutMe as string) || "",
            userName: (item.UserName as string) || "",
            lastModified: (item.LastModifiedTime as string) || "",
            rawData: item,
          };
          return result;
        }) || [];

      // 返回结果
      return {
        results: processedResults,
        totalCount: results.TotalRows || 0,
        debugInfo: {
          searchParams,
          rawResults: results,
        },
      };
    } catch (error) {
      console.error("人员搜索API错误:", error);

      // 返回错误信息但保持接口结构一致
      return {
        results: [],
        totalCount: 0,
        debugInfo: {
          error: error instanceof Error ? error.message : String(error),
          stack: error instanceof Error ? error.stack : undefined,
        },
      };
    }
  }
  public static async _getSiteSearchData(
    queryText: string = "",
    rowLimit: number = 50,
    sortByRecent: boolean = false
  ): Promise<ISiteSearchResponse> {
    try {
      // 组合查询条件：必须是站点
      const fullQuery = `(contentclass:STS_Site)${
        queryText
          ? ` AND (Title:${queryText}* OR SiteName:${queryText}* OR SiteUrl:${queryText}*)`
          : ""
      }`;

      // 定义要返回的站点属性字段（根据图片中的数据结构优化）
      const selectProperties = [
        "SiteId",
        "SiteName",
        "SiteUrl",
        "Title",
        "Description",
        "WebTemplate",
        "LastModifiedTime",
        "Created",
        "Author",
        "SiteLogo",
        "IsHubSite",
        "HubSiteId",
        "ParentSiteUrl",
        "LikesCount",
        "ViewsRecent",
        "CompatibilityLevel",
      ];

      // 构建搜索参数
      const searchParams: ISearchParams = {
        Querytext: fullQuery,
        SelectProperties: selectProperties,
        RowLimit: rowLimit,
        StartRow: 0,
        TrimDuplicates: false,
        EnableInterleaving: true,
        EnableNicknames: true,
        EnablePhonetic: true,
        HitHighlightedMultivaluePropertyLimit: 0,
        HitHighlightedProperties: ["Content", "Title", "SiteName"],
        SourceId: "8413cd39-2156-4e00-b54d-11efd9abdb89", // 站点搜索的固定SourceId
      };

      // 按最后修改时间排序
      if (sortByRecent) {
        searchParams.SortList = [
          {
            Property: "LastModifiedTime",
            Direction: 0, // 降序（最新的在前）
          },
        ];
      }

      // 执行搜索查询
      const results = await sp.search(searchParams);

      // 标准化返回结果（适配图片中的Rows数组结构）
      const processedResults =
        results.PrimarySearchResults?.map((item: Record<string, unknown>) => {
          const result: ISiteSearchResult = {
            SiteId: (item.SiteId as string) || "",
            SiteName: (item.SiteName as string) || "",
            SiteUrl: (item.SiteUrl as string) || "",
            Title: (item.Title as string) || "",
            Description: (item.Description as string) || "",
            WebTemplate: (item.WebTemplate as string) || "",
            LastModifiedTime: (item.LastModifiedTime as string | Date) || new Date(),
            Created: (item.Created as string | Date) || new Date(),
            Author: (item.Author as string) || "",
            SiteLogo: (item.SiteLogo as string) || "",
            IsHubSite: (item.IsHubSite as boolean) || false,
            HubSiteId: (item.HubSiteId as string) || "",
            ParentSiteUrl: (item.ParentSiteUrl as string) || "",
            LikesCount: (item.LikesCount as number) || 0,
            ViewsRecent: (item.ViewsRecent as number) || 0,
            CompatibilityLevel: (item.CompatibilityLevel as number) || 0,
            Rank: (item.Rank as number) || 0,
            DocId: (item.DocId as number) || 0,
            WorkId: (item.WorkId as number) || 0,
            Path: (item.Path as string) || "",
            Size: (item.Size as number) || 0,
            Culture: (item.Culture as string) || "",
            Write: (item.Write as Date) || new Date(),
            CollapsingStatus: (item.CollapsingStatus as number) || 0,
          };
          return result;
        }) || [];

      return {
        results: processedResults,
        totalCount: results.TotalRows,
      };
    } catch (error) {
      console.error("站点搜索API错误:", error);
      throw error;
    }
  }
}
